package com.youknowme.core;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.LinkedList;
import java.util.List;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;

import android.app.Application;
import android.content.Context;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.os.SystemClock;
import android.util.Log;

import com.youknowme.utility.LocalyticsHelper;

public class ApplicationWrapper extends Application {

	public static final String TAG = "GTGH_ApplicationWrapper";

	public static boolean IS_FOREGROUND = false;

	/*
	 * 存放所有activity的通讯处理器
	 */
	private static Map<String, Handler> mActivityHandlerPool = new ConcurrentHashMap<String, Handler>();

	/**
	 * 异步消息列表
	 * */
	private static List<AysncMessage> mAsynMessagePeddingList = new LinkedList<AysncMessage>();

	private boolean mIsApplictionLaunched = false;

	@Override
	public void onCreate() {
		super.onCreate();
		initUmeng();
		// 初始化图片缓存
		// ImageCache.getInstance(this).initBitmapCache(this);
		// // 酒店模块初始化
		// AppCfg.init(this, AppCfg.APP2, Constants.App.SOURCE, null, false);
		// // 酒店模块初始化：jni加密
		// AppEncoder.init(new JniEncoder());
		// // 酒店模块初始化:url跳转到其他页面的代理
		// ActionUrl.init(new ActionUrlLauncher());
		// // 酒店模块初始化:登录代理
		// LoginManager.init(new LoginLauncher());
	}
	private void initUmeng() {
		LocalyticsHelper.initLocalytics(this);
	}

	public static ApplicationWrapper getApplication(Context context) {
		return (ApplicationWrapper) context.getApplicationContext();
	}

	private enum PeddingMsgType {
		NEW_ASYN_MESSAGE, NEW_HANDLER, REMOVE_HANDLER;
	}

	/**
	 * 发送异步消息
	 * 
	 * expireTime 几秒以后失效
	 * */
	public static synchronized void sendAsynMessage(Message msg, String flag, int expireTime) {
		checkPeddingMessage(PeddingMsgType.NEW_ASYN_MESSAGE, "");
		Handler handler = mActivityHandlerPool.get(flag);
		if (null != handler) {
			handler.sendMessage(msg);
		} else {
			AysncMessage asm = new AysncMessage(msg, flag, expireTime);
			mAsynMessagePeddingList.add(asm);
		}
	}

	/*
	 * 每个Activity对应一个Handler，初始化时候入池
	 */
	public static synchronized void pushHandlerPool(String flag, Handler handler) {
		if (mActivityHandlerPool == null) {
			mActivityHandlerPool = new HashMap<String, Handler>();
		}
		mActivityHandlerPool.put(flag, handler);

		// 当有handler加入的时候应该检查它的msg数据
		checkPeddingMessage(PeddingMsgType.NEW_HANDLER, flag);
	}

	/*
	 * Activity销毁的时候，移除
	 */
	public static synchronized void popHandlerPool(String flag) {
		if (mActivityHandlerPool != null && mActivityHandlerPool.containsKey(flag)) {
			mActivityHandlerPool.remove(flag);
		}

		checkPeddingMessage(PeddingMsgType.REMOVE_HANDLER, flag);
	}

	/**
	 * 检查过期的message
	 * 
	 * NEW_ASYN_MESSAGE newMessage NEW_HANDLER new Handler REMOVE_HANDLER remove
	 * Handler
	 * */
	private static void checkPeddingMessage(PeddingMsgType state, String flag) {

		if (mAsynMessagePeddingList.size() > 0) {
			long currrentClock = SystemClock.elapsedRealtime();
			ArrayList<AysncMessage> removed = new ArrayList<AysncMessage>();
			for (AysncMessage msg : mAsynMessagePeddingList) {
				if (msg.expireTime < currrentClock) {
					removed.add(msg);
					continue;
				}

				switch (state) {
				case NEW_ASYN_MESSAGE:
					break;
				case NEW_HANDLER:
					if (flag.equals(msg.flag)) {
						removed.add(msg);
						Handler handler = mActivityHandlerPool.get(flag);
						if (null != handler) {
							handler.sendMessage(msg.msg);
						}
					}
					break;
				case REMOVE_HANDLER:
					if (flag.equals(msg.flag)) {
						removed.add(msg);
					}
					break;
				}
			}

			if (removed.size() > 0) {
				mAsynMessagePeddingList.removeAll(removed);
			}

		}
	}

	/*
	 * 通知所有Handler处理
	 */
	public static void notifyHandlerPool(int what, Bundle data) {
		if (mActivityHandlerPool == null) {
			Log.d(TAG, "没有Handler可以接受消息, what:" + what);
			return;
		}
		for (Handler handler : mActivityHandlerPool.values()) {
			Message msg = Message.obtain();
			msg.what = what;
			msg.setData(data);
			handler.sendMessageDelayed(msg, 0);
		}
	}

	public static void notifyHandlers(String[] activityNames, int what, Bundle data) {
		for (String flag : activityNames) {
			Message msg = Message.obtain();
			msg.what = what;
			msg.setData(data);
			if (mActivityHandlerPool != null && mActivityHandlerPool.containsKey(flag)) {
				mActivityHandlerPool.get(flag).sendMessageDelayed(msg, 0);
			}
		}
	}

	private static class AysncMessage {
		Message msg;
		String flag;
		long expireTime;

		AysncMessage(Message msg, String flag, long expireTime) {
			this.msg = msg;
			this.flag = flag;
			this.expireTime = SystemClock.elapsedRealtime() + expireTime;
		}
	}

	public boolean isApplicationLaunched() {
		return mIsApplictionLaunched;
	}

}
